package com.laboratory.synchronize;

/**
 * @description:
 * @author: gaochao
 * @time: 2020/11/26 10:48
 */
public class Something {

    public synchronized void isSyncA() {
        int i = 5;
        while (i-- > 0) {
            System.out.println(Thread.currentThread().getName() + " : " + i);
            try {
                Thread.sleep(500);
            } catch (InterruptedException ie) {
            }
        }
    }

    public synchronized void isSyncB() {
        int i = 5;
        while (i-- > 0) {
            System.out.println(Thread.currentThread().getName() + " : " + i);
            try {
                Thread.sleep(500);
            } catch (InterruptedException ie) {
            }
        }
    }


    public static synchronized void cSyncA() {
        int i = 5;
        while (i-- > 0) {
            System.out.println(Thread.currentThread().getName() + " : " + i);
            try {
                Thread.sleep(500);
            } catch (InterruptedException ie) {
            }
        }
    }

    public static synchronized void cSyncB() {
        int i = 5;
        while (i-- > 0) {
            System.out.println(Thread.currentThread().getName() + " : " + i);
            try {
                Thread.sleep(500);
            } catch (InterruptedException ie) {
            }
        }
    }

    /*
     * 假如有Something类的两个实例x与y，那么下列各组方法被多线程同时访问的情况是怎样的？
     * a. x.isSyncA()与x.isSyncB()
     * b. x.isSyncA()与y.isSyncA()       可以多线程同时执行
     * c. x.cSyncA()与y.cSyncB()
     * c1. x.cSyncA()与y.cSyncA() 
     * d. x.isSyncA()与Something.cSyncA()        可以多线程同时执行
     *
     *
     */

    public static void main(String[] args) {
        final Something myt1 = new Something();
        final Something x = new Something();
        final Something y = new Something();

        //同一个实例，不同的synchronized方法，对象锁有约束（同一个对象——对象锁）——a. x.isSyncA()与x.isSyncB()
        Thread test1 = new Thread(new Runnable() {
            public void run() {
                x.isSyncA();
            }
        }, "test1");
        Thread test2 = new Thread(new Runnable() {
            public void run() {
                y.isSyncB();
            }
        }, "test2");


        //不同的实例，相同的static synchronized方法，类锁具有约束（不同的对象，类锁）c1. x.cSyncA()与y.cSyncA()
        Thread testStatic1 = new Thread(new Runnable() {
            public void run() {
                x.cSyncA();
            }
        }, "testStatic1");
        Thread testStatic2 = new Thread(new Runnable() {
            public void run() {
                y.cSyncB();
            }
        }, "testStatic2");


        test1.start();
//        test2.start();
        testStatic1.start();
//        testStatic2.start();
    }


}
